/**
 * Project Name:cnsy-url-short-service
 * File Name:UploadFileController.java
 * Package Name:cn.cnsy123.shorturls.business.controller.business 
 * Date: 2020年4月6日-下午7:08:51
 * Copyright (c) 2020, yangpengfei@360@126.com All Rights Reserved. 
 *
 */

package cn.cnsy123.shorturls.api.controller.business;

import java.io.File;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Date;
import java.util.Iterator;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.io.FilenameUtils;
import org.apache.commons.lang3.RandomUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.FastDateFormat;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.multipart.commons.CommonsMultipartResolver;

import cn.cnsy123.shorturls.api.controller.result.FileUploadErrorResult;
import cn.cnsy123.shorturls.api.controller.result.FileUploadSuccessResult;
import cn.cnsy123.shorturls.api.controller.vo.FileUploadResult;
import cn.cnsy123.shorturls.api.controller.vo.SaveFileUploadLogResult;
import cn.cnsy123.shorturls.business.service.FileUploadLogService;
import cn.cnsy123.shorturls.business.util.BatchNumberUtil;
import cn.cnsy123.shorturls.business.util.FileSizeUtil;

/**
 * ClassName: UploadFileController
 * 
 * @author yangpengfei
 * @date 2020年4月6日-下午7:08:51
 * @version 1.0
 * @since JDK 1.7
 */
@Controller
@RequestMapping(value = "/file")
public class UploadFileController {
    
    private static final Logger logger = LoggerFactory.getLogger(UploadFileController.class);
    
    @Autowired
    private FileUploadLogService fileUploadLogService;
    
    @RequestMapping(value = "/upload")
    @ResponseBody
    public FileUploadResult uploadFile(HttpServletRequest request) {
        FileUploadResult fileUploadResult = new FileUploadResult(100,"本次请求不是文件处理类型");
        logger.info("上传文件开始......");
        CommonsMultipartResolver multipartResolver = new CommonsMultipartResolver(request.getSession().getServletContext());  
        if(multipartResolver.isMultipart(request)){  
            MultipartHttpServletRequest multiRequest = (MultipartHttpServletRequest)request; 
            if(multiRequest.getFileNames() != null) {
                List<FileUploadSuccessResult> successData = new ArrayList<FileUploadSuccessResult>();
                List<FileUploadErrorResult> errorData = new ArrayList<FileUploadErrorResult>();
                Iterator<String> iterator = multiRequest.getFileNames();
                logger.info("本次请求需要上传的文件列表:{}",iterator.toString());
                
                final String batchNumber = BatchNumberUtil.createNewId();
                while(iterator.hasNext()) {
                        MultipartFile file = multiRequest.getFile(iterator.next());
                        if (file != null) {
                            String myFileName = file.getOriginalFilename();
                            try {
                                if(StringUtils.isNotBlank(myFileName)) {
                                    InputStream inputStream = file.getInputStream();
                                    String fileMd5Value = DigestUtils.md5Hex(inputStream);
                                    inputStream.close();
                                    logger.info("上传文件名:{},文件MD5:{}",myFileName,fileMd5Value);
                                    SaveFileUploadLogResult queryResult = fileUploadLogService.queryFileUploadLogByfileMD5(fileMd5Value);
                                    if(queryResult != null && queryResult.getFileId() != null) {
                                        logger.error("文件已经上传过了");
                                        errorData.add(new FileUploadErrorResult(queryResult.getFileId().longValue(),myFileName,"文件已经上传过了"));
                                    }else {
                                    
                                        // 定义上传路径  
                                        final long nowLongTime = System.currentTimeMillis();
                                        final String nowDayStr = FastDateFormat.getInstance("yyyy-MM-dd").format(nowLongTime);
                                        
                                        final String filePath = new StringBuilder("D:")
                                                .append(File.separator)
                                                .append("cnsy-url-short-service-upload-catalog").append(File.separator).append(nowDayStr).toString();
                                        
                                        final String filePreName = FastDateFormat.getInstance("yyyy_MM_dd_HH_mm_ss_SSS")
                                                .format(nowLongTime);
                                        final String fileExtension = FilenameUtils.getExtension(myFileName);
                                        final String fileName = new StringBuilder().append(filePreName)
                                                .append("_").append(RandomUtils.nextInt(1, 10000))
                                                .append("_").append(nowLongTime)
                                                .append(".").append(fileExtension).toString();
                                        StringBuilder fileUploadCatalog = new StringBuilder(filePath)
                                                .append(File.separator).append(fileName);
                                        File newFile = new File(fileUploadCatalog.toString());
                                        
                                        try {
                                            file.transferTo(newFile);
                                            SaveFileUploadLogResult saveFileUploadLogResult = fileUploadLogService.saveFileUploadLog(myFileName, fileName, filePath, fileExtension, batchNumber, true,fileMd5Value);
                                            successData.add(new FileUploadSuccessResult(saveFileUploadLogResult.getFileId().longValue(),myFileName,new Date(nowLongTime),FileSizeUtil.convertCustomFileSize(file.getSize())));
                                        } catch (Exception e) {
                                            StringBuilder errorMsg = new StringBuilder().append("原始文件名:[").append(myFileName).append("],文件上传失败");
                                            logger.error(errorMsg.toString(),e);
                                            errorData.add(new FileUploadErrorResult(null,myFileName,"文件上传失败"));
                                        }
                                    }
                                }
                            }catch (Exception e) {
                                errorData.add(new FileUploadErrorResult(null,myFileName,"文件上传异常"));
                                logger.error("发生异常",e);
                            }
                        }
                    
                }
                fileUploadResult.setSuccessData(successData);
                fileUploadResult.setErrorData(errorData);
                fileUploadResult.setCode(200);
                fileUploadResult.setMsg("请求上传文件处理成功");
            }else {
                fileUploadResult = new FileUploadResult(100,"本次请求没有文件需要上传");
            }
        }
        logger.info("上传文件结束......");
        return fileUploadResult;
    }

}
